<?php
/**
 * Created by 荣耀电竞.
 * User: 林子彦 <278805354@qq.com>
 * Date: 2018/6/13 0013
 * Time: 10:12
 */

namespace App\Shop\Repositories;

use App\Shop\Exceptions\ShopException;
use App\Shop\Models\GoodsClassModel;
use App\Shop\Contracts\GoodsInterface;
use App\Shop\Models\GoodsCommonModel;
use App\Shop\Models\GoodsImagesModel;
use App\Shop\Models\GoodsModel;
use App\Shop\Models\SpecModel;
use App\Shop\Models\SpecValueModel;

/**
 * 产品类实现
 * Class DbGoodsRepository
 * @package App\Shop\Repositories
 */
class DbGoodsRepository implements GoodsInterface
{
    /**
     * @return GoodsClassModel
     */
    public function getGoodsClassModel()
    {
        return app()->make(GoodsClassModel::class);
    }

    /**
     *  规格模型
     * @return SpecModel
     */
    public function getSpecModel()
    {
        return app()->make(SpecModel::class);
    }

    /**
     * 规格值模型
     * @return SpecValueModel
     */
    public function getSpecValueModel()
    {
        return app()->make(SpecValueModel::class);
    }

    /**
     * 获取公共商品模型
     * @return GoodsCommonModel
     */
    public function getGoodsCommonModel()
    {
        return app()->make(GoodsCommonModel::class);
    }

    /**
     * 产品模型
     * @return GoodsModel
     */
    public function getGoodsModel()
    {
        return app()->make(GoodsModel::class);
    }

    /**
     * 产品图片模型
     * @return GoodsImagesModel
     */
    public function getGoodsImagesModel(){
        return app()->make(GoodsImagesModel::class);
    }

    /**
     * 获取产品列表
     * @param $where
     * @return \Illuminate\Database\Eloquent\Collection|mixed|static[]
     */
    public function getGoodsClassList($where)
    {
        return $this->getGoodsClassModel()->newQuery()->where($where)->get();
    }

    /**
     * 获取规格列表
     * @param $where
     * @return mixed|void
     */
    public function getSpecList($where)
    {
        return $this->getSpecModel()->newQuery()->where($where)->get();
    }

    /**
     * @param $goodsId
     */
    public function getGoodsCommonById($goodsId){
        //产品信息
        $goods_common_info=$this->getGoodsCommonModel()->newQuery()->where("id",$goodsId)->first();
        if(!$goods_common_info){
            throw  new ShopException(ShopException::EROOR_SHOP_GOOD_EXIT_NOT);
        }
        $goods_common_info["spec_name"]=unserialize($goods_common_info["spec_name"]);
        $goods_common_info["spec_value"]=unserialize($goods_common_info["spec_value"]);
        $goods_common_info["spec_value_key"]=array_keys($goods_common_info["spec_value"]);
        $goods_common_info["goods_storage"]= $this->getGoodsModel()->newQuery()->where("goods_commonid",$goodsId)->sum("goods_storage");
        //获取产品列表
        if(!empty( $goods_common_info["spec_name"])){

            $where=function($query) use ($goodsId) {
                $query->where("goods_commonid",$goodsId);
                $query->where("spec_id","<>","0");
            };
            $goods_list=$this->getGoodsListByCommonId($where,["goods_id","goods_commonid","spec_id","upload_id"]);
            $new_arr=array();//新的数组
            foreach ( $goods_list as $k=>$v){
                $v['goods_spec']=unserialize($v['goods_spec']);
               $new_arr[$v->spec_id]=$v;
            }

            $goods_common_info["spec_list"]=$new_arr;
            $goods_common_info["json_spec_list"]=json_encode($new_arr);
        }else{
            $goods_common_info["spec_list"]=array();
            $goods_common_info["json_spec_list"]=json_encode(array());
        }
        //获取产品图片
        $where=function($query) use ($goodsId) {
            $query->where("goods_commonid",$goodsId);
        };
        $goods_common_info["goods_img_list"]=$this->_goodsImageList($where);
        $goods_common_info["json_goods_img_list"]=json_encode($goods_common_info["goods_img_list"]);


        return $goods_common_info;
    }

    /**
     * 产品图像
     * @param $where
     * @return array
     */
     public function _goodsImageList($where){
         $goods_img_list=$this->getGoodsImagesList($where)->toArray();
         $return_arr=array();
         foreach ($goods_img_list as $k=>$v){
             $return_arr[$v['spec_id']][]=$v;
         }
         return $return_arr;
     }
    /**
     * 获取规格列表--关联规格值的列表
     * @param $where
     * @return mixed|void
     */
    public function getSpecWithValueList($where,$select="*")
    {
        return $this->getSpecModel()->newQuery()->select($select)->with(["value"])->where($where)->get();
    }

    /***
     * 获取产品列表
     * @param $goods_common_id
     */
    public function getGoodsListByCommonId($where){
         return $this->getGoodsModel()->newQuery()->where($where)->get();
    }
    /**
     * 获取产品图片
     */
    public function getGoodsImagesList($where){
        return $this->getGoodsImagesModel()->newQuery()->where($where)->get();
    }

    /**
     * 保存产品数据
     * @param $data
     * @return mixed|void
     */
    public function saveGoodsData($data)
    {

        //先验证分类是否选择到最后的分类
        $gcSubInfo = $this->getGoodsClassModel()->newQuery()->where("pid", $data["gc_id"])->first();

        if ($gcSubInfo) {
            throw new ShopException(ShopException::EROOR_SHOP_LAST_LAST_NOT);
        }
        //保存公共商品
        $common_data = $this->_saveGoodsCommon($data);
        $goods_array_id = $this->_saveGoods($data, $common_data);//将数据保存返回  产品id数组
        $this->_saveGoodsImages($data, $common_data);
        //根据产品id生成产品二维码---将它放到队列中去生成
        return $goods_array_id;
    }

    /**
     * 更新数据
     * @param $data
     * @return mixed|void
     */
    public function updateGoodsData($data){
        //先验证分类是否选择到最后的分类
        $gcSubInfo = $this->getGoodsClassModel()->newQuery()->where("pid", $data["gc_id"])->first();

        if ($gcSubInfo) {
            throw new ShopException(ShopException::EROOR_SHOP_LAST_LAST_NOT);
        }
         $common_data = $this->_updateGoodsCommon($data);
         $goods_array_id = $this->_updateGoods($data, $common_data);//将数据保存返回  产品id数组
        $this->_updateGoodsImages($data, $common_data);
        return $common_data;
    }

    /**
     *  保存到公共表中去
     */
    private function _updateGoodsCommon($param)
    {
        $data = array();
        $data["goods_name"] = $param["goods_name"];
        $data["goods_jingle"] = $param["goods_jingle"];
        $data["gc_id"] = $param["gc_id"];
        $data["gc_name"] = "分类名称";
        $data["spec_name"] = !empty($param['spec']) ? serialize($param['sp_name']) : serialize(null);
        $data["spec_value"] = !empty($param['spec']) ? serialize($param['sp_val']) : serialize(null);
        $data["brand_id"] = "11"; //品牌id
        $data["goods_image"] = $param["goods_image"];
        $data["goods_body"] = $param["goods_body"];
        $data["mobile_body"] = $param["goods_body"];
        $data["goods_price"] = $param["goods_price"];
        $data["goods_marketprice"] = $param["goods_marketprice"];
        $data["goods_serial"] = $param["goods_serial"];  //货号
        $data["goods_storage_alarm"] = $param["goods_storage_alarm"];//预警信
        $data["goods_commend"] = empty($param["goods_commend"]) ? 0 : 1;
        $data["upload_type"] = empty($param["upload_type"]) ? 0 : 1;

        // $data["goods_barcode"] = $param["goods_name"];
         if($r=$this->getGoodsCommonModel()->newQuery()->where("id",$param["id"])->updateOrCreate(["id"=>$param["id"]],$data)){
             return $r;
         }else{
              //抛出异常
             throw new ShopException(ShopException::EROOR_SHOP_GOOD_COMMON_UPDATE_NOT);
         }
    }

    public function _updateGoodsImages($param,$common_data){

        $this->getGoodsImagesModel()->newQuery()->where("goods_commonid",$common_data->id)->delete();
        if(!empty($param["default_upload_muilt"])){
            foreach ($param["default_upload_muilt"] as $upload_key=>$upload_val){
                $data=array();
                $data["goods_commonid"]=$common_data->id;
                $data["spec_id"]=$upload_key;
                foreach ($upload_val as $v){
                    if(!empty($v)){
                        $data["image_id"]=$v;
                        $this->getGoodsImagesModel()->newQuery()->create($data);
                    }
                }
            }
        }
        return array();
    }

    public function getGoodsInfo($where){
        $result1 = $this->getGoodsInfoAndPromotionById($where);
        if (empty($result1)) {
            throw ShopException(ShopException::EROOR_SHOP_GOOD_EXIT_NOT);
        }
        if ($result1['goods_body'] == '') unset($result1['goods_body']);
        if ($result1['mobile_body'] == '') unset($result1['mobile_body']);
        $result2 = $this->getGoodsCommonInfoByID(["id"=>$result1['goods_commonid']]);

        $goods_info = array_merge($result2->toArray(), $result1->toArray());
        $goods_info['spec_value'] = unserialize($goods_info['spec_value']);
        $goods_info['spec_name'] = unserialize($goods_info['spec_name']);
        $goods_info['goods_spec'] = unserialize($goods_info['goods_spec']);
        return $goods_info;
    }
    public function getGoodsInfoAndPromotionById($where){
        return $this->getGoodsModel()->newQuery()->where($where)->first();
    }
    public function getGoodsCommonInfoByID($where){
        return $this->getGoodsCommonModel()->newQuery()->where($where)->first();
    }
    /**
     *  保存到公共表中去
     */
    private function _saveGoodsCommon($param)
    {
        $data = array();
        $data["goods_name"] = $param["goods_name"];
        $data["goods_jingle"] = $param["goods_jingle"];
        $data["gc_id"] = $param["gc_id"];
        $data["gc_name"] = "分类名称";
        $data["spec_name"] = !empty($param['spec']) ? serialize($param['sp_name']) : serialize(null);
        $data["spec_value"] = !empty($param['spec']) ? serialize($param['sp_val']) : serialize(null);
        $data["brand_id"] = "11"; //品牌id
        $data["goods_image"] = $param["goods_image"];
        $data["goods_body"] = $param["goods_body"];
        $data["mobile_body"] = $param["goods_body"];
        $data["goods_price"] = $param["goods_price"];
        $data["goods_marketprice"] = $param["goods_marketprice"];
        $data["goods_serial"] = $param["goods_serial"];  //货号
        $data["goods_storage_alarm"] = $param["goods_storage_alarm"];//预警信
        $data["goods_commend"] = empty($param["goods_commend"]) ? 0 : 1;
        $data["upload_type"] = empty($param["upload_type"]) ? 0 : 1;
        // $data["goods_barcode"] = $param["goods_name"];
         if($r=$this->getGoodsCommonModel()->newQuery()->create($data)){
            return $r;
         }else{
           throw  new  ShopException(ShopException::EROOR_SHOP_GOOD_COMMON_SAVE_NOT);
         }
    }

    /**
     * 产品更新
     * @param $param
     * @param $common_data
     */
    private  function _updateGoods($param, $common_data){

        $goods_id_data=array(); //被更新的数据
        if (!empty($param['spec'])) {  //多个商品
            foreach ($param['spec'] as $k=> $value) {
                $goods = array();

                $goods = $this->_initGoodsArray($param, $common_data);
                $goods['goods_name'] = $common_data->goods_name . ' ' . implode(' ', $value['sp_value']);
                $goods['spec_id'] = $k;
                if(!empty($param['upload_type'])){
                    $goods['upload_id'] = $value["upload_id"];
                }
                $goods['goods_price'] = $value['price'];
                $goods['goods_promotion_price'] = $value['price'];
                $goods['goods_marketprice'] = $value['marketprice'] == 0 ? $common_data->goods_marketprice : $value['marketprice'];
                $goods['goods_serial'] = $value['sku'];
                $goods['goods_storage_alarm'] = intval($value['alarm']);
                $goods['goods_spec'] = serialize($value['sp_value']);
                $goods['goods_storage'] = $value['stock'];
                //$goods['goods_barcode'] = $value['barcode'];//条形码
                $goods_info=$this->getGoodsModel()->newQuery()->where("goods_commonid",$common_data["id"])->where("spec_id",$k)->first();
                if($goods_info){

                    if($this->getGoodsModel()->newQuery()->where("goods_id",$goods_info->goods_id)->update($goods)){
                        $goods_id_data[]=$goods_info->goods_id;
                    }else{
                        //抛出异常
                        throw  new  ShopException(ShopException::EROOR_SHOP_GOOD_COMMON_UPDATE_NOT);
                    }
                }else{
                    if($r=$this->getGoodsModel()->newQuery()->create($goods)){
                        $goods_id_data[]=$r->id;
                    }else{
                        //抛出异常
                        throw  new  ShopException(ShopException::EROOR_SHOP_GOOD_COMMON_UPDATE_NOT);
                    }
                }
            }
        } else {  //单个商品
            $goods_info=$this->getGoodsModel()->newQuery()->where("goods_commonid",$common_data["id"])->where("spec_id",0)->first();
            $goods = array();
            $goods = $this->_initGoodsArray($param, $common_data);
            $goods['goods_name'] = $common_data->goods_name;
            $goods['goods_price'] = $common_data->goods_price;
            $goods['goods_promotion_price'] = $common_data->goods_price;
            $goods['goods_marketprice'] = $common_data->goods_marketprice;
            $goods['goods_serial'] = $common_data->goods_serial;
            $goods['goods_storage_alarm'] = $common_data->goods_storage_alarm;
            $goods['goods_spec'] = serialize(null);
            $goods['goods_storage'] = intval($param['goods_storage']);
            $goods['goods_barcode'] = $common_data->goods_barcode;
            if($goods_info){
                if($this->getGoodsModel()->newQuery()->where("id",$goods_info->goods_id)->update($goods)){
                    $goods_id_data[]=$goods_info->goods_id;
                }else{
                    //抛出异常
                    throw  new  ShopException(ShopException::EROOR_SHOP_GOOD_COMMON_UPDATE_NOT);
                }
            }else{
                if($r=$this->getGoodsModel()->newQuery()->create($goods)){
                    $goods_id_data[]=$r["goods_id"];
                }else{
                    //抛出异常
                    throw  new  ShopException(ShopException::EROOR_SHOP_GOOD_COMMON_UPDATE_NOT);
                }
            }
        }
        //删除没用数据
        $this->getGoodsModel()->newQuery()->whereNotIn("goods_id",$goods_id_data);
        return $goods_id_data;
    }

    /**
     * 保存到产品表中去
     */
    private function _saveGoods($param, $common_data)
    {
         $return_arr=null;
        if (!empty($param['spec'])) {  //多个商品
            foreach ($param['spec'] as $k=> $value) {
                $goods = array();
                $goods = $this->_initGoodsArray($param, $common_data);
                $goods['goods_name'] = $common_data->goods_name . ' ' . implode(' ', $value['sp_value']);
                $goods['spec_id'] = $k;
                if(!empty($param['upload_type'])){
                    $goods['upload_id'] = $value["upload_id"];
                }
                $goods['goods_price'] = $value['price'];
                $goods['goods_promotion_price'] = $value['price'];
                $goods['goods_marketprice'] = $value['marketprice'] == 0 ? $common_data->goods_marketprice : $value['marketprice'];
                $goods['goods_serial'] = $value['sku'];
                $goods['goods_storage_alarm'] = intval($value['alarm']);
                $goods['goods_spec'] = serialize($value['sp_value']);
                $goods['goods_storage'] = $value['stock'];
                //$goods['goods_barcode'] = $value['barcode'];//条形码
                $return_arr[]=$this->getGoodsModel()->newQuery()->create($goods);
            }
        } else {  //单个商品
            $goods = array();
            $goods = $this->_initGoodsArray($param, $common_data);
            $goods['goods_name'] = $common_data->goods_name;
            $goods['goods_price'] = $common_data->goods_price;
            $goods['goods_promotion_price'] = $common_data->goods_price;
            $goods['goods_marketprice'] = $common_data->goods_marketprice;
            $goods['goods_serial'] = $common_data->goods_serial;
            $goods['goods_storage_alarm'] = $common_data->goods_storage_alarm;
            $goods['goods_spec'] = serialize(null);
            $goods['goods_storage'] = intval($param['goods_storage']);
            $goods['goods_barcode'] = $common_data->goods_barcode;
            $return_arr[]=$this->getGoodsModel()->newQuery()->create($goods);
        }
        return $return_arr;
    }


    private function _saveGoodsImages($param,$common_data){

        if(!empty($param["default_upload_muilt"])){
             foreach ($param["default_upload_muilt"] as $upload_key=>$upload_val){
                 $data=array();
                 $data["goods_commonid"]=$common_data->id;
                 $data["spec_id"]=$upload_key;
                 foreach ($upload_val as $v){
                     if(!empty($v)){
                         $data["image_id"]=$v;
                         $this->getGoodsImagesModel()->newQuery()->create($data);
                     }
                 }
             }
        }
        return array();
    }
    /**
     * 初始化产品值
     * @param $param
     * @param $common_data
     * @return array
     */
    public function _initGoodsArray($param, $common_data)
    {
        $data = array();
        $data["goods_commonid"] = $common_data->id;
        $data['goods_jingle'] = $common_data->goods_jingle;
        $data['gc_id'] = $common_data->gc_id;
        $data['brand_id'] = $common_data->brand_id;
        $data['spec_name'] = $common_data->spec_name;
        $data['goods_image'] = $common_data->goods_image;
        $data['goods_body'] = $common_data->goods_body;
        $data['mobile_body'] = $common_data->mobile_body;
        $data['goods_image'] = $common_data->goods_image;
        $data['goods_state'] = empty($common_data->goods_state)?1:$common_data->goods_state;
        $data['goods_verify'] = empty($common_data->goods_verify)?1:$common_data->goods_verify;
        $data['goods_commend'] = empty($common_data->goods_commend)?1:$common_data->goods_commend;
        $data['is_own_shop'] = empty($common_data->is_own_shop)?0:$common_data->is_own_shop;;
        return $data;
    }

    public function getGoodsList($where){
        return $this->getGoodsModel()->newQuery()->where($where)->get();
    }

    public function getGoodsCommonList($where){
        return $this->getGoodsCommonModel()->newQuery()->where($where)->get();
    }
}